'use strict';

layui.define(['jquery'], function(exports) {
  var $ = layui.jquery;

  var MODULE_NAME = 'affix';

  var ClassName = {
    SLOT : 'layadmin-affix-slot',
    FIXED: 'layadmin-affix-fixed'
  };

  var $win = $(window);

  function Affix() {
    this.affix = false;
    this.$el = null;
    this.$slot = null;
    this.$parent = null;
    this.config = {
      offsetTop   : 0,
      fixClassName: ''
    };
  }

  Affix.prototype.render = function(selector, options) {
    var $el = $(selector);

    if ($el.length <= 0) return;

    this.$el = $el;
    var $slot = this.$slot = $('<div class="' + ClassName.SLOT + '" style="display: none;" />');
    var $parent = this.$parent = $el.parent();
    $parent.prepend($slot);

    $.extend(this.config, options);

    // 处理方向
    var offsetBottom = this.config.offsetBottom;
    var type = 'top';
    if (typeof offsetBottom !== 'undefined' && offsetBottom >= 0) {
      type = 'bottom';
    }
    this.config.offsetType = type;
    this.bindEvents();
  };

  Affix.prototype.bindEvents = function() {
    $win.on('scroll.' + MODULE_NAME, this.handleScroll.bind(this));
    $win.on('resize.' + MODULE_NAME, this.handleScroll.bind(this));
  };

  Affix.prototype.handleScroll = function() {
    var $el = this.$el;
    var $slot = this.$slot;
    var $parent = this.$parent;
    var offsetTop = this.config.offsetTop;
    var offsetBottom = this.config.offsetBottom;
    var offsetType = this.config.offsetType;
    var fixClassName = this.config.fixClassName;

    var windowHeight = $win.height();

    var scrollTop = $win.scrollTop();
    var elOffset = $parent.offset();
    var elHeight = $slot.outerHeight();

    // Fixed Top
    if (elOffset.top - offsetTop < scrollTop && offsetType === 'top' && !this.affix) {
      this.affix = true;
      $slot.css({
        display: 'block',
        width  : $el.outerWidth(),
        height : $el.outerHeight()
      });
      $el.addClass(fixClassName).css({
        top  : offsetTop,
        left : elOffset.left,
        right: elOffset.left
      });
    } else if (elOffset.top - offsetTop > scrollTop && offsetType === 'top' && this.affix) {
      this.affix = false;
      $slot.css({
        display: 'none',
        width  : '',
        height : ''
      });
      $el.removeClass(fixClassName).css({
        top  : '',
        left : '',
        right: '',
        width: ''
      });
    }

    // Fixed Bottom
    if (elOffset.top + offsetBottom + elHeight > scrollTop + windowHeight && offsetType === 'bottom' && !this.affix) {
      this.affix = true;
      $el.addClass(fixClassName).css({
        bottom: offsetBottom,
        left  : elOffset.left,
        right : elOffset.left
      });
    } else if (elOffset.top + offsetBottom + elHeight < scrollTop + windowHeight && offsetType === 'bottom' && this.affix) {
      this.affix = false;
      $el.removeClass(fixClassName).css({
        bottom: '',
        left  : '',
        right : '',
        width : ''
      });
    }
  };

  exports(MODULE_NAME, new Affix());
});
